package top.csjss.hospital.controller;

import com.github.pagehelper.PageInfo;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.subject.Subject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.StringUtils;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import top.csjss.hospital.dto.CashierDTO;
import top.csjss.hospital.dto.ReportDTO;
import top.csjss.hospital.entity.*;
import top.csjss.hospital.enums.HospitalExceptionEnums;
import top.csjss.hospital.exception.HospitalException;
import top.csjss.hospital.service.*;
import top.csjss.hospital.vo.*;

import javax.validation.Valid;
import java.util.ArrayList;
import java.util.List;

/**
 * @Author ztf
 * @Date 10:53 2021/10/20
 **/
@RestController
public class CaoController {
    Logger log = LoggerFactory.getLogger(CaoController.class);

    @Autowired
    private ReportService reportService;
    @Autowired
    private DepartmentService departmentService;
    @Autowired
    private RegisteredTypeService registeredTypeService;
    @Autowired
    private DoctorService doctorService;
    @Autowired
    private PharmacyService pharmacyService;
    @Autowired
    private CashierService cashierService;
    @Autowired
    private OutPatientTypeService outPatientTypeService;

    /**
     * 展示挂号用户信息
     *
     * @param cc   1-查看全部，2-查看当前挂号信息，3-查看预约挂号信息
     * @param name 检索挂号用户信息的条件，并没有指定检索哪个字段
     * @return
     */
    @GetMapping("/cao/index")
    public List<ReportVO> index(@RequestParam(defaultValue = "1") Integer cc, String name) {
        //调用service查询数据
        List<ReportVO> data = reportService.findPatientInfo(cc, name);
        return data;
    }

    /**
     * 查询科室类型
     *
     * @return
     */
    @PostMapping("/cao/seldep")
    public List<DepartmentVO> SelectDepartment() {
        return departmentService.selectDepartment();
    }

    /**
     * 查询挂号类型
     *
     * @return
     */
    @PostMapping("/cao/selreg")
    public List<RegisteredTypeVO> SelectRegisteredType() {
        return registeredTypeService.selectRegisteredType();
    }

    /**
     * 查询医生信息
     *
     * @param registeredId 挂号类型ID
     * @param departmentId 科室ID
     * @return
     */
    @PostMapping("/cao/seldoctor")
    public List<DoctorVO> SelectDoctor(Integer registeredId, Integer departmentId) {
        if (registeredId == null || departmentId == null) {
            log.info("【查询医生信息】 请求参数不合法！ registeredId = {},departmentId = {}", registeredId, departmentId);
            return null;
        }
        return doctorService.selectDoctor(registeredId, departmentId);
    }

    /**
     * 查询挂号费
     *
     * @param registeredId
     * @return
     */
    @PostMapping("/cao/selRegMoney")
    public Integer SelectRegisteredMoney(Integer registeredId) {
        if (registeredId == null) {
            log.info("【查询挂号费】 请求参数不合法！ registeredId = {}", registeredId);
            return null;
        }
        return registeredTypeService.findPriceByRegisteredId(registeredId);
    }

    /**
     * 检查手机号和身份证号码
     *
     * @param phone
     * @param carid
     * @return
     */
    @PostMapping("/cao/phone")
    public Integer CheckPhoneAndCardId(String phone, String carid) {
        //校验参数
        if (StringUtils.isEmpty(phone) || StringUtils.isEmpty(carid)) {
            log.info("【手机号和身份证校验】 手机或身份证为空");
            return null;
        }
        //调用service
        return reportService.checkPhoneAndCarid(phone, carid);
    }

    /**
     * 添加患者挂号信息
     *
     * @param reportDTO
     * @return
     */
    @PostMapping("/cao/addReport")
    public R DddReport(@Valid ReportDTO reportDTO, BindingResult bindingResult) {
        if (bindingResult.hasErrors()) {
            String msg = bindingResult.getFieldError().getDefaultMessage();
            log.error("【添加患者信息】 请求参数异常，msg = {}", msg);
            return R.error(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR, msg);
        }
        //封装录入信息
        Subject subject = SecurityUtils.getSubject();
        SysUser sysUser = (SysUser) subject.getPrincipal();
        if (subject == null) {
            log.info("登录已超时");
            return R.error(HospitalExceptionEnums.LOGIN_TIMEOUT);
        }
        reportDTO.setUsers(sysUser.getRealName());
        //调用service保存
        reportService.addReport(reportDTO);

        return R.ok("患者信息保存成功");

    }

    /**
     * 删除患者信息
     *
     * @param id
     * @return
     */
    @PostMapping("/cao/delre")
    public R DeleteReport(Integer id) {
        if (id == null) {
            log.info("【删除患者信息】 参数为空");
            return R.error(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        reportService.deleteReport(id);
        return R.ok("删除患者信息成功");
    }

    /**
     * 查询患者是否有未缴费的药品
     *
     * @param reportId
     * @return
     */
    @PostMapping("/caoout/selch")
    public Integer SelectUnpaidDrugs(Integer reportId) {
        //校验
        if (reportId == null) {
            log.info("【查询患者是否有未缴费的药品】 参数为空");
            return null;
        }
        Integer i = cashierService.selectUnpaidDrugs(reportId);
        return i;
    }

    /**
     * 查询患者是否有未缴费的项目
     *
     * @param reportId
     * @return
     */
    @PostMapping("/caocc/seljiao")
    public Integer SelectUnpaidProject(Integer reportId) {
        //校验
        if (reportId == null) {
            log.info("【查询患者是否有未缴费的药品】 参数为空");
            return null;
        }
        Integer i = cashierService.selectUnpaidProject(reportId);
        return i;
    }

    /**
     * 查询患者是否有已缴费，但是未做的项目
     *
     * @param reportId
     * @return
     */
    @PostMapping("/caocc/selwei")
    public Integer SelectOutstandingProjects(Integer reportId) {
        //校验
        if (reportId == null) {
            log.info("【查询患者是否有已缴费，但是未做的项目】 参数为空");
            return null;
        }
        //校验
        Integer i = cashierService.selectOutstandingProjects(reportId);
        return i;

    }

    /**
     * 查询病因
     *
     * @param reid
     * @return
     */
    @PostMapping("/caocc/selbing")
    public String SelectCause(Integer reid) {
        //校验
        if (reid == null) {
            log.info("【查询病因】 参数为空");
            return null;
        }
        String cause = reportService.selectCause(reid);
        return cause;
    }

    /**
     * 专业操作
     *
     * @param id
     * @param zhuan
     * @return
     */
    @PostMapping("/zhuanyuan")
    public R TransferToHospital(Integer id, String zhuan) {
        if (id == null || StringUtils.isEmpty(zhuan)) {
            log.info("【转院】 id或病因为空 id{},zhuan{}", id, zhuan);
            return R.error(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }

        reportService.transferToHospital(id, zhuan);
        return R.ok("添加患者信息成功!");
    }

//======================处方划价==============================

    /**
     * 展示患者信息
     *
     * @param name
     * @param page
     * @param limit
     * @return
     */
    @GetMapping("/caotake/tselpreson")
    public R displayPatientInformation(String name, @RequestParam(defaultValue = "1") Integer page, @RequestParam(defaultValue = "10") Integer limit) {
        PageInfo<Report> pageInfo = reportService.displayPatientInformation(name, page, limit);
        //封装数据
        long count = pageInfo.getTotal();
        List<ReportVO> data = new ArrayList<>();
        for (Report report : pageInfo.getList()) {
            ReportVO vo = new ReportVO();
            BeanUtils.copyProperties(report, vo);
            data.add(vo);
        }
        return R.ok(count, data);

    }

    /**
     * 查询药品
     *
     * @param drugname
     * @param page
     * @param limit
     * @return
     */
    @GetMapping("/caocc/seldrug")
    public R selectDrugs(String drugname, @RequestParam(defaultValue = "1") Integer page, @RequestParam(defaultValue = "10") Integer limit) {
        //查询药品
        PageInfo<Pharmacy> pageInfo = pharmacyService.selectDrugs(drugname, page, limit);
        //封装
        long count = pageInfo.getTotal();
        List<DrugVO> data = new ArrayList<>();
        pageInfo.getList().forEach(pharmacy -> {
            data.add(new DrugVO(pharmacy.getPharmacyName(), pharmacy.getDrugStoreNum(), pharmacy.getUnitName(), pharmacy.getSellingPrice()));
        });

        return R.ok(data);
    }

    /**
     * 展示患者的药品出纳信息
     *
     * @param perid 当前患者id
     * @param page
     * @param limit
     * @return
     */
    @GetMapping("/caocc/selAll")
    public R selectDrugCashierInformation(Integer perid, @RequestParam(defaultValue = "1") Integer page, @RequestParam(defaultValue = "10") Integer limit) {
        //校验
        if (perid == null) {
            log.info("【展示患者的药品出纳信息】参数为空");
            return R.error(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        //调用service查询
        List<CashierVO> data = cashierService.selectDrugCashierInformation(perid, page, limit);
        return R.ok(data);
    }

    /**
     * 添加病因
     *
     * @param reid
     * @param bing
     * @return
     */
    @PostMapping("/caocc/addbing")
    public R AddEtiology(Integer reid, String bing) {
        //校验
        if (reid == null || StringUtils.isEmpty(bing)) {
            log.info("【添加病因】reid或bing为空 reid{},bing{}", reid, bing);
            return R.error(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        reportService.updateEtiology(reid, bing);

        return R.ok("添加病因成功");
    }

    /**
     * 查询患者是否开过当前处方药
     *
     * @param reid
     * @param mename
     * @return
     */
    @PostMapping("/caocc/selchu")
    public Integer SelectPrescriptionDrugs(Integer reid, String mename) {
        //校验
        if (reid == null) {
            log.info("reid为空");
            return null;
        }
        Integer i = cashierService.selectPrescriptionDrugsByCurrentPatient(reid, mename);
        return i;
    }

    /**
     * 给患者添加-修改处方信息
     *
     * @param registerId
     * @param name
     * @param num
     * @return
     */
    @PostMapping({"/caocc/addchu","/caocc/updchu"})
    public R AddPrescription(Integer registerId, String name, Integer num) {
        //校验
        if (registerId == null || StringUtils.isEmpty(name) || num == null) {
            log.info("【添加处方信息】添加失败，参数异常：registerId{},name{},num{}", registerId, name, num);
            return R.error(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        cashierService.addPrescription(registerId, name, num);
        return R.ok("添加|修改患者药品出纳信息成功!");
    }

    @PostMapping("/caocc/del")
    public R DeletePrescription(Integer id) {
        //校验
        if (id == null) {
            log.info("【删除处方】id为空");
            return R.error(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        //调用service
        R r = cashierService.deletePrescription(id);

        return r;
    }

    //========================项目划价==========================

    @GetMapping("/caocc/selpreson")
    public R SelectPreson(String name,@RequestParam(defaultValue = "1") Integer page, @RequestParam(defaultValue = "10") Integer limit) {
        PageInfo<Report> pageInfo = reportService.displayPatientInformation(name, page, limit);
        //封装数据
        long count = pageInfo.getTotal();
        List<ReportVO> data = new ArrayList<>();
        for (Report report : pageInfo.getList()) {
            ReportVO vo = new ReportVO();
            BeanUtils.copyProperties(report, vo);
            data.add(vo);
        }
        return R.ok(count, data);
    }

    /**
     * 展示项目信息
     * @param projectName
     * @param page
     * @param limit
     * @return
     */
    @GetMapping("/caoout/selout")
    public R selectProject(String projectName, @RequestParam(defaultValue = "1") Integer page, @RequestParam(defaultValue = "10") Integer limit) {
        //查询药品
        PageInfo<OutPatientType> pageInfo = outPatientTypeService.selectProject(projectName, page, limit);
        //封装
        long count = pageInfo.getTotal();
        List<OutPatientTypeVO> data = new ArrayList<>();
        pageInfo.getList().forEach(project -> {
            data.add(new OutPatientTypeVO(project.getProjectName(),project.getUnitName(),project.getPrice(),project.getOstate()));
        });
        return R.ok(data);
    }

    /**
     * 展示患者项目出纳信息
     * @param perid
     * @param page
     * @param limit
     * @return
     */
    @GetMapping("/caocc/selximu")
    public R selectProjectrInformation(Integer perid, @RequestParam(defaultValue = "1") Integer page, @RequestParam(defaultValue = "10") Integer limit) {
        if (perid==null){
            log.info("【展示患者的项目】  展示患者项目请求参数异常");
            throw new HospitalException(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        PageInfo<Cashier> pageInfo=cashierService.findProjectByReportId(perid,page,limit);
        long count = pageInfo.getTotal();
        List<Cashier> list = pageInfo.getList();
        List<CashierProjectVO> data=new ArrayList<>();
        for (Cashier cashier : list) {
            CashierProjectVO vo=new CashierProjectVO();
            BeanUtils.copyProperties(cashier,vo);
            data.add(vo);
        }
        return R.ok(count,data);
    }

    /**
     * 给患者添加项目信息
     * @param reportId
     * @param durgname
     * @param durgnum
     * @return
     */
    @PostMapping(value = {"/caoout/addchuo","/caoout/updchu"})
    public R chuProject(Integer reportId,String durgname,@RequestParam(defaultValue = "1") Integer durgnum){
        if (reportId==null||durgname==null||durgnum==null){
            log.info("【给患者添加项目信息】  给患者添加项目信息参数异常");
            throw new HospitalException(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        cashierService.updateChuProject(reportId,durgname,durgnum);
        return R.ok("给患者添加项目出纳信息成功");
    }
    /**
     * 删除患者未交费的项目出纳信息
     * @param cashier
     */
    @PostMapping(value = "/cao/delo",produces = "text/html;charset=utf-8")
    public String delo(Integer cashier){
        if (cashier==null){
            log.info("【删除患者处方信息】  删除患者处方信息参数异常");
            throw new HospitalException(HospitalExceptionEnums.REQUEST_PARAMETER_ERROR);
        }
        cashierService.remove(cashier);
        return "刪除成功";
    }

}
